-- 实现c#的Dictionary



-- 模块定义
local M = 
{
    _base_class = require "objects.Object",
    _class_name = "collections.Map"
};
setmetatable (M, {__index = _G;});
_ENV = M;

-- 引用模块
local Tools = require "tools.CommonTools"

operation_table = Tools.CreateOperationTable (_base_class); 

-- 获取字典中的键/值对数目
function operation_table.Count (self)
   return self._states._count;
end;

-- 获取字典中和指定的键关联的值，不存在返回nil
function operation_table.GetItem (self, key)
    return self._data[key];
end;

-- 设置字典中和指定的健关联的值，不存在键值时抛出错误
function operation_table.SetItem (self, key, value)
    if (self._data[key] == nil) then
        error ("Key not found in dictionary");
    end;
    self._data[key] = value;
end;

-- 将指定的键和值添加到字典中，如果键值已经存在，则抛出错误
function operation_table.Add (self, key, value)
    if (self._data[key] == nil) then
        self._data[key] = value;
        self._states._count = self._states._count + 1;
    else
        error ("Key already exist in collection");
    end;
end;

-- 移除所有的键和值
function operation_table.Clear (self)
    for key, value in pairs (self._data) do
        self._data[key] = nil;
    end;
    self._states._count = 0;
end;

-- 测试是否包含指定键
function operation_table.ContainsKey (self, key)
    return (self._data[key] ~= nil);
end;

-- 测试是否包含指定值
function operation_table.ContainsValue (self, value)
    for key, value in pairs (self._data) do
        if (value == value) then
            return true;
        end;
    end;
    return false;
end;

-- 移除指定的键对应的键/值对
function operation_table.Rmv (self, key)
    if (self._data[key] ~= nil) then
        self._states._count = self._states._count - 1;
    end;
    self._data[key] = nil;
end;

-- 返回迭代器
function operation_table.GetIter (self)
    return pairs (self._data);
end;

-- 字符串表示
function operation_table.__tostring (self)
    local map_str = "";
    for _k, _v in self:get_iter () do
        map_str = map_str .. tostring(_k) .. "=" .. tostring(_v) .. ", ";
    end;
    return "[" .. map_str .. "]";
end;

function NewMap ()
    local instance = _base_class.NewObject ();
    Tools.PrepareInstance (M, instance);

    -- 将构建map所需的状态变量保存到内部表中 
    local state_table = {};
    instance._states = state_table;
    state_table._count = 0;

    -- 键/值对被保存在另外一张内部表中
    local data_table = {};
    instance._data = data_table;

    return instance;
end;

return M;
